package com.timothy.asset.report;

import com.timothy.asset.base.Initialize;
import com.timothy.asset.data.MarketPriceUtil;
import com.timothy.asset.model.SecurityBean;
import com.timothy.asset.util.DateUtil;
import com.timothy.asset.util.NumberUtil;
import com.timothy.asset.util.SendMailUtil;
import jxl.CellView;
import jxl.Workbook;
import jxl.format.Colour;
import jxl.write.*;
import org.apache.log4j.Logger;

import java.io.*;
import java.util.ArrayList;
import java.util.List;
import java.util.StringTokenizer;

/**
 * Created with IntelliJ IDEA.
 * User: qtang
 * Date: 9/21/12
 * Time: 1:17 PM
 * To change this template use File | Settings | File Templates.
 */
public class DailyReport {

    private static Logger logger = Logger.getLogger(DailyReport.class.getName());
    private double exchangeUSDCNY;
    private double exchangeHKDCNY;
    private double totalMarketCap;


    public DailyReport() {
        exchangeUSDCNY =  Double.valueOf(MarketPriceUtil.getExchangeData("USDCNY",1));
        exchangeHKDCNY = Double.valueOf(MarketPriceUtil.getExchangeData("HKDCNY", 1));
    }

    public double getExchangeUSDCNY() {
        return exchangeUSDCNY;
    }

    public double getExchangeHKDCNY() {
        return exchangeHKDCNY;
    }

    public double getTotalMarketCap() {
        return totalMarketCap;
    }

    private WritableWorkbook createWorkbook(OutputStream stream) {
        WritableWorkbook wwb = null;
        try {
            wwb = Workbook.createWorkbook(stream);
        } catch (IOException e) {
            logger.error(e);
        }
        return wwb;
    }

    private File generateFile(Initialize init, List<SecurityBean> securityBeans) throws Exception {
        logger.debug("============= Begin generate Excel =============");
        File report = null;
        FileOutputStream out = null;
        WritableWorkbook wwb = null;
        try {
            report = new File("MyAssets" + DateUtil.getCurrentDate() + ".xls");
            out = new FileOutputStream(report);
            wwb = createWorkbook(out);
            WritableSheet sheet = wwb.createSheet("result", 0);

            // Format the Font
            WritableFont wf = new WritableFont(WritableFont.ARIAL, 10, WritableFont.BOLD);
            WritableCellFormat cf = new WritableCellFormat(wf);
            cf.setBackground(Colour.GRAY_25);

            String reportHeader = init.getPropertyValue("report_header");
            StringTokenizer st = new StringTokenizer(reportHeader, ",");
            int col = 0;
            while (st.hasMoreTokens()) {
                String s_title = st.nextToken();
                Label cl = new Label(col++, 0, s_title, cf);
                sheet.addCell(cl);
            }

            //write content

            CellView cv = new CellView();
            cv.setAutosize(true);

            int rowIndex = 0;
            for (SecurityBean bean : securityBeans) {
                sheet.setColumnView(0, cv);
                sheet.setColumnView(1, cv);
                sheet.setColumnView(2, cv);
                sheet.setColumnView(3, cv);
                sheet.setColumnView(4, cv);
                sheet.setColumnView(5, cv);

                rowIndex++;
                sheet.addCell(new Label(0, rowIndex, bean.getAccount()));

                if(bean.getCode()!=null){
                    sheet.addCell(new Label(1, rowIndex, bean.getCode()));
                }
                if(bean.getName()!=null){
                    sheet.addCell(new Label(2, rowIndex, bean.getName()));
                }
                if(bean.getMarketPrice()>0.0){
                    sheet.addCell(new Label(3, rowIndex, NumberUtil.formatData4Deci(bean.getMarketPrice())));
                }
                if(bean.getAmount()> 0.0){
                    sheet.addCell(new Label(4, rowIndex, NumberUtil.formatData2Deci(bean.getAmount())));
                }
                sheet.addCell(new Label(5, rowIndex, NumberUtil.formatData2Deci(bean.getMarketCap())));
            }
        } catch (FileNotFoundException e) {
            logger.error(e);
        } catch (WriteException e) {
            logger.error(e);
        } finally {
            try {
                if (wwb != null) {
                    wwb.write();
                    wwb.close();
                }
                if (out != null) {
                    out.close();
                }

            } catch (WriteException e) {
                logger.error(e);
            }
        }
        logger.debug("============= End generate Excel =============");
        return report;
    }

    private List<SecurityBean> getData(Initialize init){
        List<SecurityBean> securityList = new ArrayList<SecurityBean>();

        //get A account security data
        String securityAccountA = init.getPropertyValue("security_account_a");
        String securityAccountACash = init.getPropertyValue("security_account_a_cash");
        String securityCodeList = init.getPropertyValue("security_code_list");
        String securityAmountList = init.getPropertyValue("security_amount_list");
        StringTokenizer stSecurityCode = new StringTokenizer(securityCodeList, ",");
        String[] securityAmountArray = securityAmountList.split(",");
        double totalMarketCap = 0;
        int i = 0;
        while (stSecurityCode.hasMoreTokens()) {
            String s_Code = stSecurityCode.nextToken();
            String s_Name = MarketPriceUtil.getSingleSecurityData(s_Code,0);
            double s_marketPrice = MarketPriceUtil.getSingleStockPrice(s_Code);
            double s_Amount = Double.valueOf(securityAmountArray[i]);
            double s_marketCap =  s_marketPrice * s_Amount;
            totalMarketCap+= s_marketCap ;
            securityList.add(new SecurityBean(securityAccountA,s_Code, s_Name, s_marketPrice, s_Amount, s_marketCap));
            i++;
        }
        SecurityBean cash = new SecurityBean();
        cash.setAccount(securityAccountA+" Cash");
        cash.setMarketCap(Double.valueOf(securityAccountACash));
        securityList.add(cash);

        //get B account security data
        String securityAccountB = init.getPropertyValue("security_account_b");
        String securityAccountBHKDCash = init.getPropertyValue("security_account_b_cash_hkd");
        String securityAccountBUSDCash = init.getPropertyValue("security_account_b_cash_usd");
        String securityCodeBList = init.getPropertyValue("security_code_list_b");
        String securityAmountBList = init.getPropertyValue("security_amount_list_b");
        StringTokenizer stSecurityBCode = new StringTokenizer(securityCodeBList, ",");
        String[] securityAmountBArray = securityAmountBList.split(",");


        int j = 0;
        double exchangeRate = 1.0;
        while (stSecurityBCode.hasMoreTokens()) {

            String s_Code = stSecurityBCode.nextToken();
            String s_Name = MarketPriceUtil.getSingleSecurityData(s_Code,0);
            double s_marketPrice = MarketPriceUtil.getSingleStockPrice(s_Code);
            double s_Amount = Double.valueOf(securityAmountBArray[j]);
            double s_marketCap =  s_marketPrice * s_Amount;
            if(s_Code.startsWith("sz")){
                exchangeRate = getExchangeHKDCNY();
            }
            if(s_Code.startsWith("sh")){
                exchangeRate = getExchangeUSDCNY();
            }

            double s_marketCap2RMB = s_marketCap * exchangeRate;
            totalMarketCap+= s_marketCap2RMB ;

            securityList.add(new SecurityBean(securityAccountB,s_Code, s_Name, s_marketPrice, s_Amount, s_marketCap2RMB));
            j++;
        }
        if(securityAccountBHKDCash!=null&&securityAccountBHKDCash.length()>0){
            SecurityBean cashB = new SecurityBean();
            cashB.setAccount(securityAccountB+" Cash");
            cashB.setMarketCap(Double.valueOf(securityAccountBHKDCash)*getExchangeHKDCNY());
            securityList.add(cashB);
        }

        if(securityAccountBUSDCash!=null&&securityAccountBUSDCash.length()>0){
            SecurityBean cashB = new SecurityBean();
            cashB.setAccount(securityAccountB+" Cash");
            cashB.setMarketCap(Double.valueOf(securityAccountBUSDCash)*getExchangeUSDCNY());
            securityList.add(cashB);
        }


        SecurityBean total = new SecurityBean();
        total.setAccount("Total");
        total.setMarketCap(totalMarketCap);
        securityList.add(total);

        this.totalMarketCap = totalMarketCap;

        return securityList;
    }

    public static void main(String[] args) {
        Initialize init = Initialize.getInstance();
        StringBuffer content = new StringBuffer();
        if (init.isInitSuccessfully()) {
            DailyReport report = new DailyReport();
            List<SecurityBean> securityBeans = report.getData(init);
            File rptFile;
            try {
                rptFile = report.generateFile(init,securityBeans);
                SendMailUtil sendMail = new SendMailUtil();
                content.append("Hi Timothy,\n") ;
                content.append("\n") ;
                content.append("     This is a daily report for your financial assets.\n") ;
                content.append("\n") ;

                content.append("Total marketcap:"+ NumberUtil.formatData2Deci(report.getTotalMarketCap()) +" RMB\n");
                content.append("\n") ;
                content.append("Exchange:\n");
                content.append("HKDCNY:"+report.getExchangeHKDCNY()+"\n");
                content.append("USDCNY:"+report.getExchangeUSDCNY()+"\n");
                content.append("\n") ;
                content.append("\n") ;
                content.append("Regards,\n");
                content.append("Timothy\n");

                sendMail.setMsgContent(content.toString());
                sendMail.addAttachFile(rptFile.getName());
                sendMail.sendMail(sendMail.getSession());
            } catch (Exception e) {
                e.printStackTrace();  //To change body of catch statement use File | Settings | File Templates.
            }
        }

    }

}
